package com.dhecp.project.purchase.service.impl;

import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.alibaba.fastjson.JSON;
import com.dhecp.common.core.domain.AjaxResult;
import com.dhecp.common.utils.MessageUtils;
import com.dhecp.common.utils.RandomValueUtils;
import com.dhecp.common.utils.TypeUtils;
import com.dhecp.core.constant.DataFiltering;
import com.dhecp.core.utils.PageUtils;
import com.dhecp.core.utils.ReflectUtils;
import com.dhecp.framework.util.ShiroUtils;
import com.dhecp.project.common.domain.ModuleNID;
import com.dhecp.project.common.domain.RecordCheck;
import com.dhecp.project.common.domain.UpdateFlow;
import com.dhecp.project.common.mapper.ModuleNidAndBidMapper;
import com.dhecp.project.common.service.impl.BaseModuleServiceImpl;
import com.dhecp.project.flowable.mapper.SysProcessInstanceMapper;
import com.dhecp.project.flowable.service.ActProcessService;
import com.dhecp.project.purchase.domain.DistributionSon;
import com.dhecp.project.purchase.domain.PurchaseAddress;
import com.dhecp.project.purchase.domain.PurchasePlan;
import com.dhecp.project.purchase.domain.PurchasePlanSon;
import com.dhecp.project.purchase.mapper.DistributionSonMapper;
import com.dhecp.project.purchase.mapper.PurchaseAddressMapper;
import com.dhecp.project.purchase.mapper.PurchasePlanMapper;
import com.dhecp.project.purchase.mapper.PurchasePlanSonMapper;
import com.dhecp.project.purchase.service.PurchasePlanService;
import com.dhecp.project.system.service.SysDictionaryForFieldService;

/**
 * @program: kjecp
 * @description: 采购计划 (主表-母件
 * @author: hlf
 * @create: 2022-08-15 11:44
 */
@Service
public class PurchasePlanServiceImpl extends BaseModuleServiceImpl implements PurchasePlanService {

    @Autowired
    private PurchasePlanMapper purchaseMapper;
    @Autowired
    private PurchasePlanSonMapper sonMapper;
    @Autowired
    private PurchaseAddressMapper addressMapper;
    @Autowired
    private DistributionSonMapper distributionMapper;

    @Autowired
    private ModuleNidAndBidMapper moduleNidAndBidMapper;
    @Autowired
    private ActProcessService actProcessService;
    @Autowired
    private SysProcessInstanceMapper processInstanceMapper;
    @Autowired
    private SysDictionaryForFieldService dictionaryForFieldService;

    /**
     * @Description: 查询前一单NID、BID
     * @Param: [params] nid 必要参数：当前 单据编码
     * @return: com.dhecp.common.core.domain.AjaxResult  (data.nid 前一单NID， data.bid 前一单BID)
     * @Author: hlf
     * @date: 2022-05-09 10:08
     */
    @Override
    public AjaxResult queryLastNid(Map<String, Object> params) throws Exception {
        Map<String, Object> dataMap = new HashMap<String, Object>();
        if (params.get("nid") == null || params.get("nid") == "") {
            params.put("nid", "0");
        }
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_SCODE, dictionaryForFieldService.getDataScode(params));    //数据权限查询条件SQL语句
        ModuleNID moduleNID = purchaseMapper.selectLastNid(params);
        if (moduleNID == null) {
            dataMap.put("nid", "0");
            dataMap.put("bid", "0");
            return AjaxResult.warn(MessageUtils.message("module.warn.isfirstnid"), TypeUtils.mapToJson(dataMap).toString());
        }
        dataMap.put("nid", moduleNID.getNid().toString());
        dataMap.put("bid", moduleNID.getBid().toString());
        return AjaxResult.success(MessageUtils.message("module.success.issuccess"), TypeUtils.mapToJson(dataMap).toString());
    }


    /**
     * @Description: 查询后一单NID、BID
     * @Param: [params] nid 必要参数：当前 单据编码
     * @return: com.dhecp.common.core.domain.AjaxResult  (data.nid 后一单NID， data.bid 后一单BID)
     * @Author: hlf
     * @date: 2022-05-09 10:09
     */
    @Override
    public AjaxResult queryNextNid(Map<String, Object> params) throws Exception {
        Map<String, Object> dataMap = new HashMap<String, Object>();
        if (params.get("nid") == null || params.get("nid") == "" || "0".equals(params.get("nid").toString())) {
            dataMap.put("nid", "0");
            dataMap.put("bid", "0");
            return AjaxResult.warn(MessageUtils.message("module.warn.isfinallynid"), TypeUtils.mapToJson(dataMap).toString());
        }
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_SCODE, dictionaryForFieldService.getDataScode(params));    //数据权限查询条件SQL语句
        ModuleNID moduleNID = purchaseMapper.selectNextNid(params);
        if (moduleNID == null) {
            dataMap.put("nid", "0");
            dataMap.put("bid", "0");
            return AjaxResult.warn(MessageUtils.message("module.warn.isfinallynid"), TypeUtils.mapToJson(dataMap).toString());
        }
        dataMap.put("nid", moduleNID.getNid().toString());
        dataMap.put("bid", moduleNID.getBid().toString());
        return AjaxResult.success(MessageUtils.message("module.success.issuccess"), TypeUtils.mapToJson(dataMap).toString());
    }

    @Override
    public PurchasePlan queryFirstRecord(Map<String, Object> params) throws Exception {
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_SCODE, dictionaryForFieldService.getDataScode(params));    //数据权限查询条件SQL语句
        return purchaseMapper.selectFirstRecordByNid(params);
    }

    @Override
    public List<PurchasePlan> queryListByNid(Map<String, Object> params) throws Exception {
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_SCODE, dictionaryForFieldService.getDataScode(params));    //数据权限查询条件SQL语句
        return purchaseMapper.selectByNid(params);
    }

    @Override
    public List<PurchasePlan> queryList(Map<String, Object> params) throws Exception {
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_WHERE, dictionaryForFieldService.getWhereStr(params));    //常规查询条件SQL语句
        params.put(DataFiltering.DATA_SCODE, dictionaryForFieldService.getDataScode(params));    //数据权限查询条件SQL语句
        PageUtils.startPageStronger();
        return purchaseMapper.select(params);
    }

    @Override
    public List<PurchasePlan> queryList2(Map<String, Object> params) throws Exception {
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_WHERE, dictionaryForFieldService.getWhereStr(params));    //常规查询条件SQL语句
        params.put(DataFiltering.DATA_SCODE, dictionaryForFieldService.getDataScode(params));    //数据权限查询条件SQL语句
        PageUtils.startPageStronger();
        return purchaseMapper.select2(params);
    }

    @Override
    public List<PurchasePlanSon> querySonListBm(Map<String, Object> params) throws Exception {
        return sonMapper.queryListBm(params);
    }

    @Override
    public List<PurchasePlanSon> querySonListNid(String fNid) throws Exception {
        return sonMapper.queryListNid(fNid);
    }


    @Override
    public List<PurchasePlan> queryGroupList(Map<String, Object> params) throws Exception {
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_WHERE, dictionaryForFieldService.getWhereStr(params));    //常规查询条件SQL语句
        params.put(DataFiltering.DATA_SCODE, dictionaryForFieldService.getDataScode(params));    //数据权限查询条件SQL语句
        PageUtils.startPageStronger();
        return purchaseMapper.selectgroup(params);
    }


    /**
     * @Description: 查询已选择的数据
     * @Param: [params]
     * @return: java.util.List<com.dhecp.project.system.domain.SysUserInfoSimple>
     * @Author: hlf
     * @date: 2022-08-18 17:14
     */
    @Override
    public List<PurchasePlan> querySelectList(Map<String, Object> params) throws Exception {
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_WHERE, dictionaryForFieldService.getWhereStr(params));        //常规查询条件SQL语句
        if (params.containsKey("selIdList")) {
            params.put("selIdList", params.get("selIdList").toString().split(","));
        }
        if (params.get("field") == null || params.get("field") == "") {
            String orderBy = "spBm asc";
            PageUtils.startPageOrder(orderBy);
        } else {
            PageUtils.startPage();
        }
        return purchaseMapper.querySelectList(params);
    }


    /**
     * @Description: 查询已选择的数据
     * @Param: [params]
     * @return: java.util.List<com.dhecp.project.system.domain.SysUserInfoSimple>
     * @Author: hlf
     * @date: 2022-08-18 17:14
     */
    @Override
    public List<PurchasePlan> querySelectList2(Map<String, Object> params) throws Exception {
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_WHERE, dictionaryForFieldService.getWhereStr(params));        //常规查询条件SQL语句
        if (params.containsKey("selIdList")) {
            params.put("selIdList", params.get("selIdList").toString().split(","));
        }
        if (params.get("field") == null || params.get("field") == "") {
            String orderBy = "bid asc";
            PageUtils.startPageOrder(orderBy);
        } else {
            PageUtils.startPage();
        }
        return purchaseMapper.querySelectList2(params);
    }

    /**
     * @Description: 根据母件获取之间 (多条
     * @Param: [fBm]
     * @return: java.util.List<com.dhecp.project.business.domain.ProductBasisComponent>
     * @Author: hlf
     * @date: 2022-08-18 17:14
     */
    @Override
    public List<PurchasePlanSon> querySonListByFBm(Map<String, Object> params) throws Exception {
        params.put(DataFiltering.TABLE_ALIAS, "t1");    //查询表别名
        params.put(DataFiltering.DATA_WHERE, dictionaryForFieldService.getWhereStr(params));        //常规查询条件SQL语句
        if (params.get("field") == null || params.get("field") == "") {
            String orderBy = "fBm asc";
            PageUtils.startPageOrder(orderBy);
        } else {
            PageUtils.startPage();
        }
        return sonMapper.querySonListByFBm(params);
    }

    /**
     * @Description: 根据母件获取子件间 (多条
     * @Param: [fBm]
     * @return: java.util.List<com.dhecp.project.business.domain.ProductBasisComponent>
     * @Author: hlf
     * @date: 2022-08-18 17:14
     */
    @Override
    public List<PurchasePlanSon> querySonListByFBm2(Map<String, Object> params) throws Exception {
        if (params.get("field") == null || params.get("field") == "") {
            String orderBy = "t2.bid asc";
            PageUtils.startPageOrder(orderBy);
        } else {
            PageUtils.startPage();
        }
        return sonMapper.querySonListByFBm2(params);
    }

    @SuppressWarnings("unchecked")
    @Override
    public AjaxResult saveData(Map<String, Object> params) {
        params.put("businessEntity", new PurchasePlan());

        PurchasePlan onData = JSON.parseObject(params.get("infoMap").toString(), PurchasePlan.class);
        if (!(onData.getPlanCost()>0)){
            return AjaxResult.error("采购计划预估金额，不可为0");
        }
        List<PurchasePlan> purchasePlanList = JSON.parseArray(params.get("infoItems").toString(), PurchasePlan.class);
        Map<String, Object> guidMap = new HashMap<String, Object>();
        String resNid = null;
        for (PurchasePlan plan : purchasePlanList
        ) {
            List<PurchasePlanSon> onSonData = new ArrayList<>();
            if (params.containsKey("sonData")) {
                onSonData = JSON.parseArray(params.get("sonData").toString(), PurchasePlanSon.class);
            }
            for (PurchasePlanSon item:onSonData
                 ) {

                //判断是否铺货
                if (onData.getSort().equals("线上")){
                    DistributionSon distributionSon = distributionMapper.findById(item.getsBm());

                    if (distributionSon == null){
                        return AjaxResult.error("该商品未铺货完整，请联系客服人员");
                    }
                }

            }

            AjaxResult ajaxResult = this.saveDataBase(params);
            Map<String, Object> infoMap = (Map<String, Object>) ajaxResult.get("infoMap");
            resNid = infoMap.get("nid").toString();

            List<RecordCheck> guidMapList = purchaseMapper.findRecords(infoMap.get("nid").toString());


            if (!guidMapList.isEmpty()) {
                if (infoMap.get("newNid") != null && "1".equals(infoMap.get("newNid").toString())) { //单号重复验证
                    throw new RuntimeException(MessageUtils.message("module.error.retry"));
                }
                for (RecordCheck recordCheck : guidMapList) {
                    if (recordCheck != null && recordCheck.getGuid() != null) {
                        guidMap.put(recordCheck.getGuid().toString(), "1");
                    }
                }
            }

            resNid = infoMap.get("nid").toString();
            String guid = "";
            if (plan.getGuid() == null) {
                guid = RandomValueUtils.getGUID();
                plan.setGuid(guid);
            } else {
                guid = plan.getGuid().toString();
            }

            for (String field : infoMap.keySet()) { //遍历非网格字段，并赋值到实体中
                Object fieldValue = infoMap.get(field);
                ReflectUtils.setValue(plan, field, fieldValue);
            }

            Map<String, Object> params2 = new HashMap<String, Object>();
            params2.put("guid",plan.getAddressId());
            PurchaseAddress purchaseAddress = addressMapper.findById(params2);
            if (purchaseAddress != null){
                plan.setPhone(purchaseAddress.getPhone());//联系电话
                plan.setvBank(purchaseAddress.getvBank());//开户行
                plan.setvAccount(purchaseAddress.getvAccount());//银行账号
                plan.setvTax(purchaseAddress.getvTax());//税号
                plan.setvJydz(purchaseAddress.getvJydz());//经营地址
                plan.setvKpdh(purchaseAddress.getvKpdh());//开票电话
                plan.setvKpdz(purchaseAddress.getvKpdz());//开票地址
                plan.setvGsfr(purchaseAddress.getvGsfr());//公司法人
                plan.setvLxdh(purchaseAddress.getvLxdh());//联系电话
                plan.setvFax(purchaseAddress.getvFax());//传真
                plan.setvGjH(purchaseAddress.getvGjH());//所在国家
                plan.setvSfH(purchaseAddress.getvSfH());//省份
                plan.setvDsH(purchaseAddress.getvDsH());//城市
                plan.setvCqH(purchaseAddress.getvCqH());//城区
                plan.setvDzH(purchaseAddress.getvDzH());//街道
                plan.setvYbH(purchaseAddress.getvYbH());//邮编
                plan.setvFhr(purchaseAddress.getvFhr());//发货人
                plan.setvFhrSj(purchaseAddress.getvFhrSj());//发货人手机
                plan.setvFhrDh(purchaseAddress.getvFhrDh());//发货人电话
                plan.setvGjP(purchaseAddress.getvGjP());//国家 票
                plan.setvSfP(purchaseAddress.getvSfP());//省份 票
                plan.setvDsP(purchaseAddress.getvDsP());//城市 票
                plan.setvCqP(purchaseAddress.getvCqP());//城区 票
                plan.setvDzP(purchaseAddress.getvDzP());//地址 票
                plan.setvYbP(purchaseAddress.getvYbP());//邮编 票
                plan.setvSpr(purchaseAddress.getvSpr());//收票人
                plan.setvSprSj(purchaseAddress.getvSprSj());//收票人手机
                plan.setvSprDh(purchaseAddress.getvSprDh());//收票人电话
                plan.setInvoiceType(purchaseAddress.getInvoiceType());//发票类型
            }

            Double cost = 0.00;

            List<PurchasePlanSon> oldData = sonMapper.queryListNid(resNid);
            if (oldData.size() > 0) {
                for (PurchasePlanSon item : oldData
                ) {
                    sonMapper.delete(item);
                }
            }


            for (PurchasePlanSon item : onSonData
            ) {
                if (item.getfBm().equals(plan.getSpBm())){
                    item.setGuid(RandomValueUtils.getGUID());
                    item.setCreateTime(new Date());
                    item.setfNid(resNid);
                    cost = cost + item.getTotalPrices();
                    sonMapper.insert(item);
                }

            }

            plan.setPlanCost(cost);
            if (guidMap.get(guid) == null) {
                purchaseMapper.insert(plan);
            } else {
                purchaseMapper.update(plan);
                guidMap.remove(guid);
            }

        }

        if (!guidMap.isEmpty()) {
            for (String guid : guidMap.keySet()) {
                purchaseMapper.delete(guid);
            }
        }

        return AjaxResult.success(MessageUtils.message("module.success.issuccess"), resNid);
    }


    /**
     * 修改审核状态
     *
     * @param guid
     * @return
     * @author DH-Xxj
     */
    @Override
    public AjaxResult updateType(Map<String, Object> params) {
        List<PurchasePlan> purchasePlan = purchaseMapper.findByIdList(params);
        for (PurchasePlan item : purchasePlan
        ) {
            item.setvType(Integer.valueOf(params.get("vType").toString()));
            item.setUpdateTime(new Date());
            purchaseMapper.update(item);
        }
        return AjaxResult.success(MessageUtils.message("module.success.issuccess"));
    }


    /**
     * 采购订单生成
     *
     * @param infoItems
     * @return
     * @author DH-Xxj
     */
    @Override
    public AjaxResult updateOrder(Map<String, Object> params) throws Exception {
        List<PurchasePlan> purchasePlanList = JSON.parseArray(params.get("infoItems").toString(), PurchasePlan.class);
        if (purchasePlanList == null || purchasePlanList.size() == 0) {
            return AjaxResult.error(MessageUtils.message("module.error.jsontoentyerror"));
        }
        for (PurchasePlan item : purchasePlanList) {
            if (item.getSort().equals("线上")){
                purchaseMapper.createOrder(item);
                item.setOrderState("订单已生成");
                purchaseMapper.updateOrderState(item);
            }
        }
        return AjaxResult.success(MessageUtils.message("module.success.issuccess"));
    }

    /**
     * 删除采购数据
     *
     * @param nid
     * @return
     * @author DH-Xxj
     */
    @Override
    public AjaxResult delete(Map<String, Object> params) {
        params.put("nid", params.get("nid").toString());
        List<PurchasePlan> businessDataList = purchaseMapper.selectByNid(params);
        if (businessDataList.size() > 0) {
            //删除单据时，先删除未完成的流程任务
            String procInstId = businessDataList.get(0).getProcInstId();
            if (procInstId != null && !"".equals(procInstId)) {
                actProcessService.deleteProcess(procInstId);
                //插入指定单据流转各环节审批人记录（单据删除记录）
                Map<String, Object> flowRecord = new HashMap<String, Object>();
                flowRecord.put("moduleTable", params.get("moduleTable").toString());
                flowRecord.put("nid", businessDataList.get(0).getNid());
                flowRecord.put("activeFlowOld", "FlowZd");
                flowRecord.put("procInstId", procInstId);
                flowRecord.put("createUser", ShiroUtils.getMandatorId());
                flowRecord.put("createUserName", ShiroUtils.getMandatorName());
                flowRecord.put("updateUsers", "实际删除操作人： " + ShiroUtils.getUserName() + "【" + ShiroUtils.getUserId() + "】");
                flowRecord.put("optType", "delete");
                processInstanceMapper.insertProcessInstanceFlowRecord(flowRecord);
            }
        }
        purchaseMapper.deleteNid(params.get("nid").toString());
        return AjaxResult.success(MessageUtils.message("module.success.issuccess"));
    }


    /**
     * @Description: 流转  —— 添加流程任务、修改流程状态及生效标志
     * @Param: [params] tableDataId 必要参数：单据编码（nid）
     * @return: com.dhecp.common.core.domain.AjaxResult
     * @Author: hlf
     * @date: 2022-05-09 10:11
     */
    @Override
    public AjaxResult updateFlowGo(Map<String, Object> params) {
        Map<String, Object> infoMap = new HashMap<String, Object>();
        String nid = "0";
        if (params.get("tableDataId") == null || params.get("tableDataId") == "") {
            return AjaxResult.error(MessageUtils.message("module.error.lack", "单据编码【tableDataId】"));
        } else {
            nid = params.get("tableDataId").toString();
        }
        params.put("nid", nid);
        List<PurchasePlan> businessDataList = purchaseMapper.selectByNid(params);
        if (businessDataList == null || businessDataList.size() == 0) {
            return AjaxResult.error(MessageUtils.message("module.error.nodata"));
        } else {
            if (!(businessDataList.get(0).getPlanCost()>0)){
                return AjaxResult.error("采购计划预估金额，不可为0!");
            }

            infoMap.put("cid", businessDataList.get(0).getCid());
            infoMap.put("bUser", businessDataList.get(0).getbUser());
            infoMap.put("bDept", businessDataList.get(0).getbDept());
            infoMap.put("procInstId", businessDataList.get(0).getProcInstId());
            infoMap.put("activeFlow", businessDataList.get(0).getActiveFlow());
            infoMap.put("createTime", businessDataList.get(0).getCreateTime());
            params.put("infoMap", TypeUtils.mapToJson(infoMap).toString());
            params.put("activeFlowOld", businessDataList.get(0).getActiveFlow());

        }

        //流程处理公共方法，返回单据（流转、回退等）后的流程状态信息
        if (params.get("optType") == null || params.get("optType") == "") {
            params.put("optType", "go");
        }
        UpdateFlow updateFlow = new UpdateFlow();

        updateFlow = this.FlowDealBase(params);

        for (PurchasePlan businessData : businessDataList) {
            updateFlow.setGuid(businessData.getGuid());
            purchaseMapper.updateFlow(updateFlow);
        }

        return AjaxResult.success(MessageUtils.message("module.success.issuccess"), nid);
    }

    /**
     * @Description: 退回  —— 添加流程任务、修改流程状态及生效标志
     * @Param: [params] tableDataId 必要参数：单据编码（nid）
     * @return: com.dhecp.common.core.domain.AjaxResult
     * @Author: hlf
     * @date: 2022-05-09 10:11
     */
    @Override
    public AjaxResult updateFlowBack(Map<String, Object> params) {
        Map<String, Object> infoMap = new HashMap<String, Object>();
        String nid = "0";
        if (params.get("tableDataId") == null || params.get("tableDataId") == "") {
            return AjaxResult.error(MessageUtils.message("module.error.lack", "单据编码【tableDataId】"));
        } else {
            nid = params.get("tableDataId").toString();
        }
        params.put("nid", nid);
        List<PurchasePlan> businessDataList = purchaseMapper.selectByNid(params);
        if (businessDataList == null || businessDataList.size() == 0) {
            return AjaxResult.error(MessageUtils.message("module.error.nodata"));
        } else {
            infoMap.put("cid", businessDataList.get(0).getCid());
            infoMap.put("bUser", businessDataList.get(0).getbUser());
            infoMap.put("bDept", businessDataList.get(0).getbDept());
            infoMap.put("procInstId", businessDataList.get(0).getProcInstId());
            infoMap.put("activeFlow", businessDataList.get(0).getActiveFlow());
            infoMap.put("createTime", businessDataList.get(0).getCreateTime());
            params.put("infoMap", TypeUtils.mapToJson(infoMap).toString());
            params.put("activeFlowOld", businessDataList.get(0).getActiveFlow());
        }

        //流程处理公共方法，返回单据（流转、回退等）后的流程状态信息
        if (params.get("optType") == null || params.get("optType") == "") {
            params.put("optType", "back");
        }
        UpdateFlow updateFlow = new UpdateFlow();
        updateFlow = this.FlowDealBase(params);

        for (PurchasePlan businessData : businessDataList) {
            updateFlow.setGuid(businessData.getGuid());
            purchaseMapper.updateFlow(updateFlow);
        }

        return AjaxResult.success(MessageUtils.message("module.success.issuccess"), nid);
    }

}
